package com.mju.controller;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.mju.controller.common.BaseController;
import com.mju.controller.common.JsonResult;
import com.mju.controller.ex.*;
import com.mju.pojo.User;
import com.mju.service.IUserService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import springfox.documentation.spring.web.json.Json;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;
import java.io.File;
import java.io.IOException;
import java.util.Map;
import java.util.UUID;

// 采用Restful风格，编写请求路径。
@RestController
@RequestMapping("/users")
@Api(tags = "用户信息服务")
public class UserController extends BaseController {
    @Autowired
    private IUserService userService;

    @ApiOperation("用户注册")
    @PostMapping("/reg")
    public JsonResult<Void> reg(@RequestBody User user) { // @RequestBody：前端就可以传递json数据了，方便接受。
        // 创建响应结果对象
        JsonResult<Void> result = new JsonResult<>();
        // 调用业务层的注册方法
        userService.registor(user);
        result.setStatus(OK);
        result.setMessage("用户注册成功");
        return result;
    }

    @ApiOperation("用户注册(新版)")
    @PostMapping("/new_reg")
    public JsonResult new_reg(@RequestBody User user) {
        //  新用户默认用户名为邮箱
        user.setUsername(user.getEmail());
        // 调用业务层的注册方法
        String message = userService.new_registor(user) ? "用户注册成功，等待激活" : "用户注册失败，请重新注册";
        return new JsonResult(OK,message);
    }

    @ApiOperation("修改用户状态")
    @PutMapping("/updateStatus")
    public JsonResult updateStatus(@RequestParam("uid") Integer uid,@RequestParam("status")  Integer status){
        String message = userService.updateStatus(uid, status) ? "修改状态成功" : "修改状态失败";
        return new JsonResult(OK,message);
    }


    @ApiOperation("用户登录")
    @PostMapping("/login")
    public JsonResult<User> login(@RequestBody User user) {
        User data = userService.login(user.getUsername(), user.getUserpassword());
        //System.out.println(data);
        // 获取token
        //String token = getToken(data.getId()+"", data.getUsername());
        String token = getToken(data.getId() + "", data.getUsername());
        //System.out.println("token:" + token);

        // 解析token
        //System.out.println("解析：" + parseTokenGetUidAndUname(token));

        return new JsonResult<User>(OK, data, token);
    }

    @ApiOperation("修改密码")
    @PostMapping("/change_password")
    public JsonResult<Void> changePassword(String oldPassword,
                                           String newPassword,
                                           HttpServletRequest request) {
        //System.out.println("old:" + oldPassword);
        //System.out.println("new:" + newPassword);
        // 修改密码功能，要先登陆后，才能操作哦
        String token = request.getHeader("Authorization");
        Map<String, String> map = parseTokenGetUidAndUname(token);
        String uid = map.get("uid");
        String username = map.get("uname");

        userService.changePassword(Integer.valueOf(uid), username, oldPassword, newPassword);
        return new JsonResult<>(OK);
    }

    /**
     * 一打开个人资料页面，就发送一个查询，获取数据信息
     * @param request 主要用于获取当前页面的id信息
     * @return
     */
    @ApiOperation("根据id查询用户")
    @GetMapping("/get_by_id")
    public JsonResult<User> getById(HttpServletRequest request) {
        // 获取token
        String token = request.getHeader("Authorization");
        // 解析token
        String uid = parseTokenGetUid(token);

        System.out.println("uid: " + uid);
        // 获取对应的数据
        User data = userService.getById(Integer.valueOf(uid));
        // 返回
        return new JsonResult<User>(OK, data);
    }

    @ApiOperation("根据用户id查询用户")
    @GetMapping("/getUser/{uid}")
    public JsonResult<User> getUserById(@PathVariable("uid") Integer uid) {
        User data = userService.getById(uid);
        return new JsonResult<User>(OK, data);
    }
    @ApiOperation("根据用户名查询用户")
    @GetMapping("/getUserByUname/{uname}")
    public JsonResult<User> getUserByUname(@PathVariable("uid") String uname) {
        Integer uid = userService.getUidByUname(uname);
        User data = userService.getById(uid);
        return new JsonResult<User>(OK, data);
    }

    // 点击修改按钮，修改用户信息
    @ApiOperation("修改用户信息")
    @PostMapping("/change_info")
    public JsonResult<Void> changeInfo(@RequestBody User user, HttpServletRequest request) {
        // 注意：user对象有四个数据：username, phone, email, gender
        // 控制层将token中的id传递给业务层，业务层再将id封装到user对象中
        String token = request.getHeader("Authorization");
        String uid = parseTokenGetUid(token);
        userService.changeInfo(Integer.valueOf(uid), user); // 内部会进行id的封装
        return new JsonResult<>(OK);
    }

    // 头像上传(较复杂)
    @ApiOperation("头像上传")
    @PostMapping("/change_avatar")
    public JsonResult<String> changeAvatar(HttpServletRequest request, HttpSession session, MultipartFile file) {// 注：file要与input标签的name属性一致
        if(file.isEmpty()) {// 判断文件是否为空
            throw new FileEmptyException("文件为空");
        }
        if(file.getSize() > AVATAR_MAX_SIZE) {
            throw new FileSizeException(("文件超出限制"));
        }
        // 判断文件的类型是否是我们规定的后缀类型
        String contentType = file.getContentType();
        // AVATAR_TYPE是集合
        if(!AVATAR_TYPE.contains(contentType)) {
            throw new FileTypeException("文件类型不支持");
        }

        // 上传的文件路径: .../upload/文件名.jpg
        // 注意：getServletContext()：获取当前应用程序的上下文，每次启动tomcat都会创建新的上下文
        String parent = session.getServletContext().getRealPath("/upload");
        // 用下面的路径(拦截器要进行相应的映射配置哦)
        //String parent = "/tmp-images"; // 会自动映射到static下的upload文件夹下
        // 判断路径是否存在
        File dir = new File(parent);
        if(!dir.exists()) {
            dir.mkdirs();
        }
        // 获取文件名称+后缀
        String originalFilename = file.getOriginalFilename();
        int index = originalFilename.lastIndexOf(".");
        String suffix = originalFilename.substring(index); // 获取后缀
        String filename = UUID.randomUUID().toString().toUpperCase() + suffix; // 具体的文件名+后缀
        // 在dir所指的对象下，创建文件
        File dest = new File(dir, filename);
        try {
            file.transferTo(dest); // 上传头像
        } catch (FileStatusException e) {
            throw new FileStatusException("文件状态异常");
        } catch (IOException e) {
            throw new FileUploadIOException("文件读写异常");
        }
        //Integer id = getIdFromSession(session);
        //String username = getUsernameFromSession(session);

        String token = request.getHeader("Authorization");
        Map<String, String> map = parseTokenGetUidAndUname(token);
        String uid = map.get("uid");
        String uname = map.get("uname");

        //String avatar = "/tmp-images/" + filename;
        String avatar = "/upload/"+filename;
        // 数据库要存储头像信息、修改人、修改时间
        userService.changeAvatar(Integer.valueOf(uid), avatar, uname);
        return new JsonResult<>(OK, avatar); // 将头像传递给前端页面。
    }


    @ApiOperation("无条件查询所有用户信息")
    @GetMapping("/queryAll/{currentPage}/{pageSize}")
    public JsonResult<IPage<User>> queryAllUsers(@PathVariable("currentPage") Integer currentPage,
                                                 @PathVariable("pageSize") Integer pageSize) {
        IPage<User> data = userService.queryAllUsers(currentPage, pageSize);
        return new JsonResult<>(OK, data);
    }

    @ApiOperation("删除用户")
    @DeleteMapping("/deleteUser/{uid}")
    public JsonResult<Integer> deleteUserByUid(@PathVariable("uid") Integer uid) {
        Integer rows = userService.deleteUserByUid(uid);
        return new JsonResult<>(OK, rows);
    }

    @ApiOperation("添加用户")
    @PostMapping("/addUser")
    public JsonResult<Integer> addUser(@RequestBody User user) {
        Integer data = userService.addUser(user);
        return new JsonResult<>(OK, data);

    }

    @ApiOperation("修改用户是否为VIP和会员名称")
    @PutMapping("/updateIsVipAndVipName")
    public JsonResult<String> updateIsVipAndVipName(
            @RequestParam("uid") Integer uid, @RequestParam("status") Integer status, @RequestParam("vipName") String vipName) {
        String message = userService.updateIsVipAndVipName(uid, status, vipName) > 0 ? "修改成功" : "修改失败";
        return new JsonResult<>(OK,message);
    }

    @ApiOperation("修改用户是否为VIP")
    @PutMapping("/updateIsVip")
    public JsonResult<String> updateIsVip(
            @RequestParam("uid") Integer uid, @RequestParam("status") Integer status) {
        String message = userService.updateIsVip(uid, status) > 0 ? "修改成功" : "修改失败";
        return new JsonResult<>(OK, message);
    }

    @ApiOperation("获取用户id，根据用户名")
    @GetMapping("/getUidByUname/{uname}")
    public JsonResult<Integer> getUidByUname(@PathVariable String uname) {
        Integer data = userService.getUidByUname(uname);
        return new JsonResult<>(OK, data);
    }

    @ApiOperation("修改用户信息")
    @PutMapping("/updateUser/{uid}")
    public JsonResult<Integer> updateUser(@PathVariable Integer uid, @RequestBody User user) {
        Integer data = userService.updateUser(uid, user);
        return new JsonResult<>(OK, data);
    }

    @ApiOperation("重置密码")
    @PutMapping("/resetPassword/{uid}")
    public JsonResult<Void> resetPassword(@PathVariable("uid") Integer uid) {
        userService.resetPassword(uid);
        return new JsonResult<>(OK);
    }
}
